package com.ltu.timkor6.gamesite.client;

import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.user.client.ui.Anchor;
import com.google.gwt.user.client.ui.HorizontalPanel;
import com.google.gwt.user.client.ui.Label;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.SimplePanel;
import com.google.gwt.user.client.ui.VerticalPanel;
import com.google.gwt.user.client.ui.Widget;
import com.ltu.timkor6.gamesite.admin.client.Admin;
import com.ltu.timkor6.gamesite.games.memory.client.Memory;
import com.ltu.timkor6.gamesite.games.missingbits.client.MissingBits;
import com.ltu.timkor6.gamesite.games.suduku.client.Suduku;
import com.ltu.timkor6.gamesite.games.towerofhanoi.client.TowerOfHanoi;
import com.ltu.timkor6.gamesite.listings.client.Listings;
import com.ltu.timkor6.gamesite.shared.UserInfo;
import com.ltu.timkor6.gamesite.users.client.Users;

/**
 * Entry point classes define <code>onModuleLoad()</code>.
 */
public class GameSite implements EntryPoint
{
	private Users users;
	
	private VerticalPanel menuUsers;
	private VerticalPanel menuTestCreator;
	private VerticalPanel menuAdmin;
	
	private HorizontalPanel body;
	private VerticalPanel menu;
	private SimplePanel content;

	
	/**
	 * This is the entry point method.
	 */
	public void onModuleLoad()
	{
		this.users = new Users(this);
		
		// Check if user is logged in.
		this.users.checkIfLoggedIn();
	}
	
	public void loadModules()
	{
		UserInfo userInfo = this.users.getUserInfo();
		
		body = new HorizontalPanel();
		body.setStyleName("body");
		RootPanel.get("body").add(body);
		
		drawHeader();
		drawMenu(userInfo);
		drawContent();
		
		if(userInfo == null)
		{
			this.menuSignedOut();
		}
		else
		{
			this.menuSignedIn();
		}
	}
	
	private void drawHeader()
	{
		
	}
	
	private void drawMenu(UserInfo userInfo)
	{
		menu = new VerticalPanel();
		menu.setStyleName("game-menu");
		
		final Label menuHeader = new Label("Menu");
		menuHeader.addStyleName("menu-header");
		
		final Anchor menuMainPage = new Anchor("Main Page", "#mainpage");
		menuMainPage.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleMainPage();
			}
		});
		
		// Header
		menu.add(menuHeader);
		menu.add(menuMainPage);
		
		
		// Games
		VerticalPanel menuGames = new VerticalPanel();
		menuGames.setStyleName("menu-list");
		
		// Create game menu content
		menuGames(menuGames);
		
		menu.add(menuGames);
		
		
		if(userInfo != null)
		{
			if(userInfo.isTestUser())
			{
				this.menuTestCreator();
			}
			if(userInfo.isAdmin())
			{
				this.menuAdmin();
			}
		}
		
		this.body.add(this.menu);
	}

	private void menuGames(VerticalPanel menuGames)
	{
		
		// Title Games
		Label titleUsers = new Label("Games");
		titleUsers.addStyleName("menu-title");
		menuGames.add(titleUsers);
		
		// Memory
		final Anchor memory = new Anchor("Memory", "#game/memory");
		memory.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleGameMemory();
			}
		});
		menuGames.add(memory);
		
		// Missing Bits
		final Anchor missingBits = new Anchor("Missing Bits", "#game/missingbits");
		missingBits.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleGameMissingBits();
			}
		});
		menuGames.add(missingBits);
		
		// Suduku
		final Anchor suduku = new Anchor("Suduku", "#game/suduku");
		suduku.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleGameSuduku();
			}
		});
		menuGames.add(suduku);
		
		// Tower of Hanoi
		final Anchor towerOfHanoi = new Anchor("Tower Of Hanoi", "#game/towerofhanoi");
		towerOfHanoi.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleGameTowerOfHanoi();
			}
		});
		menuGames.add(towerOfHanoi);
	}
	
	private void drawContent()
	{
		this.content = new SimplePanel();
		this.content.setStyleName("game-content");
		
		this.moduleMainPage();
		
		this.body.add(this.content);
	}
	
	private void moduleMainPage()
	{
		VerticalPanel main = new VerticalPanel();
		
		Label header = new Label("Welcome");
		header.setStyleName("panelHeader");
		main.add(header);
		
		Label text = new Label("Please enjoy the games we provide.");
		main.add(text);
		
		this.setContent(main);
	}
	
	// Enable module greetings
	private void moduleGameMemory()
	{
		this.setContent(new Memory(users).getComposite());
	}
	
	// Enable module greetings
	private void moduleGameMissingBits()
	{
		this.setContent(new MissingBits(users).getComposite());
	}
	
	// Enable module greetings
	private void moduleGameSuduku()
	{
		this.setContent(new Suduku(users).getComposite());
	}
	
	// Enable module greetings
	private void moduleGameTowerOfHanoi()
	{
		this.setContent(new TowerOfHanoi(users).getComposite());
	}
	
	// Enable module to sign in
	private void moduleListings(boolean all)
	{
		this.setContent(new Listings(all).getComposite());
	}
	
	// Enable module to sign in
	public void moduleSignIn()
	{
		this.setContent(users.getSignInComposite());
	}
	
	private void moduleSignOut()
	{
		this.users.sendSignOut();
	}
	
	private void moduleRegister()
	{
		this.setContent(users.getRegisterComposite());
	}
	
	public void changeSignedIn()
	{
		// Change the menu
		UserInfo userInfo = this.users.getUserInfo();
		
		if(userInfo != null)
		{
			if(userInfo.isTestUser())
			{
				this.menuTestCreator();
			}
			if(userInfo.isAdmin())
			{
				this.menuAdmin();
			}
			
			this.menuUsers.removeFromParent();
			this.menuSignedIn();
			this.moduleMainPage();
		}
		else
		{
			this.menuUsers.removeFromParent();
			this.menuSignedOut();
		}
	}
	
	private void menuSignedIn()
	{
		// Users
		this.menuUsers = new VerticalPanel();
		this.menuUsers.setStyleName("menu-list");
		menu.add(this.menuUsers);
		
		// Title Users
		Label titleUsers = new Label("Users");
		titleUsers.addStyleName("menu-title");
		this.menuUsers.add(titleUsers);
		
		// Users toplist
		Anchor userList = new Anchor("UserList", "#userlist");
		userList.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleListings(false);
			}
		});
		this.menuUsers.add(userList);
		
		// Total toplist
		Anchor topList = new Anchor("TopList", "#toplist");
		topList.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleListings(true);
			}
		});
		this.menuUsers.add(topList);
		
		// Profile
		Anchor profile = new Anchor("Profile", "#profile");
		profile.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleProfile();
			}
		});
		this.menuUsers.add(profile);
		
		// Sign out
		Anchor signOut = new Anchor("Sign Out", "#signout");
		signOut.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleSignOut();
			}
		});
		this.menuUsers.add(signOut);
	}

	private void menuSignedOut()
	{
		if(this.menuTestCreator != null)
		{
			this.menuTestCreator.removeFromParent();
			this.menuTestCreator = null;
		}
		if(this.menuAdmin != null)
		{
			this.menuAdmin.removeFromParent();
			this.menuAdmin = null;
		}
		
		// Users
		this.menuUsers = new VerticalPanel();
		this.menuUsers.setStyleName("menu-list");
		menu.add(this.menuUsers);
		
		// Title Users
		Label titleUsers = new Label("Users");
		titleUsers.addStyleName("menu-title");
		this.menuUsers.add(titleUsers);
		
		// Sign In
		Anchor signIn = new Anchor("Sign In", "#signin");
		signIn.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleSignIn();
			}
		});
		this.menuUsers.add(signIn);
		
		// Register
		Anchor register = new Anchor("Register", "#register");
		register.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleRegister();
			}
		});
		this.menuUsers.add(register);
		
		// Register
		Anchor forgotten = new Anchor("Forgotten password", "#forgotten");
		forgotten.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleForgottenPassword();
			}
		});
		this.menuUsers.add(forgotten);
	}

	private void menuTestCreator()
	{
		this.menuTestCreator = new VerticalPanel();
		menuTestCreator.setStyleName("menu-list");
		menu.add(menuTestCreator);
		
		// Title Test Creator
		Label titleUsers = new Label("Test Creator");
		titleUsers.addStyleName("menu-title");
		this.menuTestCreator.add(titleUsers);
		
		// Sign In
		Anchor create = new Anchor("Create", "#test/create");
		create.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleCreateTest();
			}
		});
		this.menuTestCreator.add(create);
		
		// Register
		Anchor show = new Anchor("Show tests", "#test/show");
		show.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleShowTests();
			}
		});
		this.menuTestCreator.add(show);
	}
	
	private void menuAdmin()
	{
		this.menuAdmin = new VerticalPanel();
		menuAdmin.setStyleName("menu-list");
		menu.add(menuAdmin);
		
		// Title Admin
		Label titleUsers = new Label("Admin");
		titleUsers.addStyleName("menu-title");
		this.menuAdmin.add(titleUsers);
		
		/*
		// Add user
		Anchor addUsers = new Anchor("Add User", "#admin/addUsers");
		addUsers.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleAdminAddUsers();
			}
		});
		this.menuAdmin.add(addUsers);
		*/
		
		// List users
		Anchor listUsers = new Anchor("List Users", "#admin/listUsers");
		listUsers.addClickHandler(new ClickHandler()
		{
			public void onClick(ClickEvent event)
			{
				moduleAdminListUsers();
			}
		});
		this.menuAdmin.add(listUsers);
	}
	
	/*
	private void moduleAdminAddUsers()
	{
		// TODO Auto-generated method stub
	}
	*/

	private void moduleAdminListUsers()
	{
		this.setContent(new Admin(this).showUserList());
	}

	private void moduleShowTests() {
		// TODO Auto-generated method stub
		
	}

	private void moduleCreateTest() {
		// TODO Auto-generated method stub
		
	}

	private void moduleProfile()
	{
		this.setContent(this.users.getProfileComposite());
	}
	
	private void moduleForgottenPassword()
	{
		this.setContent(this.users.getForgottenComposite());
	}
	
	public void setContent(Widget child)
	{
		this.content.clear();
		this.content.add(child);
	}
}
